import tracker from '../utils/tracker'
import onLoad from '../utils/onLoad'
import getLastEvent from '../utils/getLastEvent'
import getSelector from '../utils/getSelector'

export function injectTiming(){
  let LCP,FMP
  
  if(PerformanceObserver){
    // FMP 首次有意义绘制获取
    new PerformanceObserver((entryList,observer)=>{
      const performanceEntries = entryList.getEntries()
      FMP = performanceEntries[0]
      observer.disconnect() // 取消订阅
      // https://developer.mozilla.org/en-US/docs/Web/API/PerformanceObserver/supportedEntryTypes
    }).observe({entryTypes:['element']})
    // 最大内容渲染
    new PerformanceObserver((entryList,observer)=>{
      const perEntry = entryList.getEntries()
      const lastEntry = perEntry[perEntry.length - 1]
      LCP = lastEntry
      observer.disconnect()
    }).observe({entryTypes:['largest-contentful-paint']})

    // 用户首次和页面交互(单击链接，点击按钮等)到页面响应交互的时间
    new PerformanceObserver((entryList,observer)=>{
      const lastEvent = getLastEvent()
      const firstInput = entryList.getEntries()[0]
      // 获取首次交互
      if(firstInput){
        // 处理延迟
        const inputDelay = firstInput.processingStar - firstInput.startTime
        // 处理耗时
        const duration = firstInput.duration
        if(inputDelay > 0 || duration >0){
          tracker.send({
            kind:"experience",
            type:"firstInputDelay",
            inputDelay:inputDelay ? fromTime(inputDelay) : '0',
            duration:duration ? fromTime(duration) : '0',
            startTime:firstInput.startTime,
            selector:lastEvent ? getSelector(lastEvent.path || lastEvent.target) : ''
          })
        }
      }
      observer.disconnect()
    }).observe({entryTypes:['first-input'],buffered:true})
  }
  // 性能指标
  onLoad(function(){
    // 加载时间收集监控
    setTimeout(()=>{
      const timings = performance.getEntries()
      const {unloadEventStart,unloadEventEnd,domInteractive,domContentLoadedEventStart,domContentLoadedEventEnd,domComplete,loadEventStart,loadEventEnd,redirectStart,redirectEnd,fetchStart,domainLookupStart,domainLookupEnd,connectStart,connectEnd,requestStart,requestEnd,responseStart,responseEnd,secureConnectionStart,duration} = timings[0]
      tracker.send({
        kind:'experience',
        type:"timing",
        unloadTime:unloadEventEnd - unloadEventStart, // 前一个页面卸载耗时 unloadEventEnd – unloadEventStart
        redirectTime:redirectEnd - redirectStart, // 重定向事件 redirectEnd - redirectStart
        appCacheTime:domainLookupStart - fetchStart, // 缓存读取时间 domainLookupStart - fetchStart
        dnsTime:domainLookupEnd - domainLookupStart, // 预名解析时长 domainLookupEnd - domainLookupStart
        tcpTime:connectEnd - connectStart, // tcp连接耗时 connectEnd - connectStart
        sslTime:connectEnd - secureConnectionStart, // 安全连接建立耗时 connectEnd - secureConnectionStart
        requestTime:responseStart - requestStart, //网络请求耗时 requestEnd - requestStart
        responsetime:responseEnd - responseStart, // 响应耗时 responseEnd - responseStart
        domTime:domInteractive - responseEnd, // dom解析耗时 domInteractive - responseEnd
        dclTime:domContentLoadedEventEnd - domContentLoadedEventStart, // 	DOMContentLoaded 事件耗时
        resourcesTime:domComplete - domContentLoadedEventEnd, // 资源加载耗时
        domReadyTime:domContentLoadedEventEnd - fetchStart, // dom阶段渲染总耗时
        onLoadTime:loadEventEnd - loadEventStart,// onLoad耗时 
        duration:duration,
        timeToInteractive:domInteractive - fetchStart, // 首次可交互时间
      })

      // 首次自定义背景绘制
      // 性能指标
      const FP = window.performance.getEntriesByName('first-paint')[0]
      // 首次内容绘制
      const FCP = window.performance.getEntriesByName('first-content-paint')[0]
      tracker.send({
        kind:"experience",
        type:'paint',
        firstPaint:FP ? fromTime(FP.startTime) : '0',
        firstContentPaint:FCP ? fromTime(FCP.startTime) : '0',
        firstMeaningfulPaint:FMP ? fromTime(FMP.startTime) : '0',
        largestContentfulPaint:LCP ? fromTime(LCP.startTime) : '0'
      })
    },3000)
  })
}

function fromTime(time){
  return `${time}`.split(".")[0]
}